﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace _05_链表
{
    class Program
    {
        static void Main(string[] args)
        {
            //尼玛啊，这书上写的代码就喜欢这样让人看不懂，其实吧 就那么点东西，搞那么复杂做什么
            //还是有点复杂，回头看吧，脑子晕
            PriorityDocumentManager pdm = new PriorityDocumentManager();
            
            pdm.AddDocument(new Document("one", "sample", 8));
            pdm.AddDocument(new Document("two", "sample", 3));
            pdm.AddDocument(new Document("three", "sample", 4));
            pdm.AddDocument(new Document("four", "sample", 8));
            pdm.AddDocument(new Document("five", "sample", 1));
            pdm.AddDocument(new Document("six", "sample", 9));
            pdm.AddDocument(new Document("seven", "sample", 1));
            pdm.AddDocument(new Document("eight", "sample", 1));
            pdm.DisplayAllNodes();
            Console.ReadKey();
        }
    }
    //文档类，没什么东西
    public class Document
    {
        /// <summary>
        /// 几个描述文档类的属性
        /// </summary>
        public string Title { get; private set; }//标题
        public string Content { get; private set; }//内容
        public byte Priority { get; private set; }//优先级
        //构造函数
        public Document(string title, string content, byte priority = 0)
        {
            this.Title = title;
            this.Content = content;
            this.Priority = priority;
        }
    }
    public class PriorityDocumentManager
    {
        private readonly LinkedList<Document> documentList;//文档链表
        private readonly List<LinkedListNode<Document>> priorityNodes;//优先级的节点列表
        //构造函数
        public PriorityDocumentManager()
        {
            documentList = new LinkedList<Document>();//文档的列表
            priorityNodes = new List<LinkedListNode<Document>>(10);//优先级节点
            for (int i = 0; i < 10; i++)
            {
                priorityNodes.Add(new LinkedListNode<Document>(null));
            }
        }
        //增加文档对象
        public void AddDocument(Document d)
        {
            if (d == null) throw new ArgumentNullException("d");
            AddDocumentToPriorityNode(d, d.Priority);
        }
        //增加文档：有优先节点参数
        private void AddDocumentToPriorityNode(Document doc, int priority)
        {
            //不能超出0-9优先级的元素
            if (priority>9||priority<0)
            {
                throw new ArgumentException("请输入在0-9之间的数");
            }
            //第一次插入时
            if (priorityNodes[priority].Value==null)
            {
                --priority;
                if (priority>=0)
                {
                    AddDocumentToPriorityNode(doc, priority);
                }
                else
                {
                    //压根不可能有else，我去
                    documentList.AddLast(doc);
                    priorityNodes[doc.Priority] = documentList.Last;
                }
                return;
            }
            else
            {
                //不是第一次插入时
                LinkedListNode<Document> prioNode = priorityNodes[priority];//优先级节点下的元素
                if (priority==doc.Priority)//和传入的document元素的有限比较，如果相等，则插入下一级，同时修改优先级
                {
                    documentList.AddAfter(prioNode, doc);
                    priorityNodes[doc.Priority] = prioNode.Next;

                }
                else
                {
                    LinkedListNode<Document> firstPrioNode = prioNode;
                    while (firstPrioNode.Previous!=null&&firstPrioNode.Previous.Value.Priority==prioNode.Value.Priority)
                    {
                        firstPrioNode = prioNode.Previous;
                        prioNode = firstPrioNode;
                    }
                    documentList.AddBefore(firstPrioNode, doc);
                    priorityNodes[doc.Priority] = firstPrioNode.Previous;
                }
            }
        }
        //显示所有节点的元素
        public void DisplayAllNodes()
        {
            foreach (Document  doc in documentList)
            {
                Console.WriteLine("priority: {0}, title: {1}",doc.Priority,doc.Title);
            }
        }
        //获取文档：返回值是document类型
        public Document GetDocument()
        {
            Document doc = documentList.First.Value;
            documentList.RemoveFirst();
            return doc;
        }
    }
}
